The Widget Factory is a suite of software products which supports the rapid design and development of Graphical User Interfaces based on X and OSF/Motif, and which also allows GUI developers to interactively design new widget classes compatible with the OSF/Motif widgets. This product gives developers the flexibility of designing and incorporating precisely the graphical objects they need into their interfaces. The design process being interactive, the Widget Factory achieves even higher reductions in development time and cost over traditional programming methods than GUI design tools.
The Widget Factory has three main components that interact with one another:
The Draw Library - the library of basic graphic reactive objects implemented as Xt gadgets.
XDrawMaker - the interactive tool for the creation of animated graphics out of the primitives of the Draw Library.
XFaceMaker - NSL's interactive UIMS (User Interface Management System), used in the Widget Factory for its capability of generating Xt or C++ classes out of animated drawings created with XDrawMaker.
The creation of a widget class in the Widget Factory involves the following steps:
The output of XDrawMaker is a file containing a description of the widgets used in the animated drawings and of their resources. Resources include the scripts that describe the drawing's animation. The description file uses a simple and legible description language - the "fm format" - also used by XFaceMaker for describing Motif graphic interfaces.
A class designed by the Widget Factory is derived from the basic classes of the Draw Library. Otherwise it does not depend on other libraries. In particular, the animation part of the widget class designed is expressed in C code and the Xlib and Xt libraries. In other words, designing animation and widget classes does not entail any loss in performance.
The C++ classes generated are wrappers around the corresponding Xt classes with data and function members added. These classes can be used in a C++ program like any other set of classes both for creating instances or for derivation of new C++ classes.
These tools are tightly coupled as will be explained below.
Let us illustrate the capabilities of the Widget Factory with some typical applications.
Many applications need dials: industrial control simulation, flight simulators and many other applications that may want to use a special dial metaphor.
Dials such as an altimeter can be easily designed with the Widget Factory.
The Widget Factory will generate not just one dial but the class corresponding to a whole set of altimeters that will differ from one another by the values of various resources. You can cre ate as many instances of it as you wish, either within a program or with a user interface build ing tool such as XFaceMaker.
The dial is scalable, that is you can create different instances with different sizes. The drawing of the dial is always drawn in relative coordinates. When used with XFaceMaker, you simply drag the icon in the right position and the widget will automatically scale the drawing accordingly.
Here are two instances of the same altimeter class with different sizes:
For the dial class you create with the Widget Factory you can define additional resources corresponding to various features. For example, you can define a resource called "altitude" that will control the position of the needle. Like any X resource, it can be set or controlled at runtime from within a program or from X resource files.
Almost any parameter can be defined as an X resource. Here are two instances of a thermometer whose resources are the minimum and the maximum temperature, the number of divisions and of subdivisions per division:
Dials may change at run time depending on the values of resources.
Here is an example of an automobile gas gauge with an alert lamp that lights up when the level is too low. This behavior is part of the widget and has been programmed into it. The application that uses the widget does not have to worry about lighting the alarm lamp when the level is too low. The widget will automatically do it for any value of the level below a predefined threshold value. In addition, the value of the threshold can also be defined as a resource, thus allowing the definition of different instances with different alarm levels.
By the way, the value of the threshold can be defined as a resource, thus allowing you to design different instances with different alarm levels.
Behavior in the Widget Factory is specified in scripts. Scripts are programs written in a C-like programming language. The Widget Factory lets you edit scripts and test them on the fly because the Widget Factory has a built-in script interpreter. Scripts are useful in many situations as we shall see.
One not so obvious situation in which scripts are useful is worth talking about even now. It concerns the two resources that we have discussed above for setting the number of divisions and subdivisions of the dial. The code for the scale generated by the Widget Factory contains a procedure for drawing the right number of divisions and subdivisions after reading the corresponding resources. This script is called when the dial is drawn on the screen and the scale designer can specify it in the form of a script. Thus scripts actually have many uses and give a lot of power and flexibility to the Widget Factory.
Many applications must draw data graphs in different shapes. With the Widget Factory one can easily draw charts and decorate them in ways not possible with ready-made data visualization widgets.
Ready-made widgets are the right choice in many cases, but are not without problems altogether. Typically, they are loaded with features, but in any given case you use only a very small fraction of them. For example, a good graphing widget can display data in the form of data graphs, bar charts or pie charts. But if you display the data as a pie chart you don't need the bar chart facility. The Widget Factory solves this problem, by letting you design a charting widget that has just the features that you need.
Here is an example of a charting application drawn with the Widget Factory.
The charts can be made to react to user input. In the picture above, the curve has been charted by means of polygonal lines. The lines are reactive: by clicking on one the user can move its control points. The machinery necssar y for using such a line as an input device is built into the polyline gadget used here. In the Widget Factory it is possible to define a "callback" of the polyline that will transmit to the application the position of its control points when the mouse is released.
The Widget Factory has the functionality for designing animated diagrams. An example of such a diagram is shown below and represents the animated diagram of a heating installation.
This diagram is not designed to become a widget class, but it could very well become one. The passive drawing, that is the drawing without the animation part, has been created first with XDrawMaker. For the creation of passive drawings, XDrawMaker has basically the functionality of a good drawing tool on personal computers. The animation has been added later in the form of scripts. For example, there is a script that moves the propeller in the mixing tank and another one that describes the motion of fluid in pipes or in the tanks.
Once created, the drawing can be printed and it can be imported in a special window in the interface of the final application. The interface of the final application, comprising the window and perhaps additional Motif widgets, can be created in a number of different ways - either by direct programming or, better, by a tool for the design of Motif user interfaces such as XFaceMaker.
The picture below is an interface in which the animated drawing created with XDrawMaker has been imported into a user interface created with XFaceMaker.
Notice the additional Motif widgets that surround the drawing. Some of these Motif widgets have been placed within the drawing, others surround the drawing. The inclusion of Motif widgets and of primitive graphics widgets is only possible because both are X Intrinsics widgets, contained and managed by the same container widget. In older systems that implement the graphic primitives in proprietary object models instead of the Xt model, it is only possible to surround an animated drawing with Motif objects but it is not possible to include Motif widgets in the drawing and to animate in a uniform manner graphics and Motif objects.
Another interesting application of the Widget Factory is the design of animated charts, such as flowcharts. To enable this the Widget Factory supports the easy construction of links between objects. Slots can be associated with a graphic object such as a rectangle or a picture. Slots can be connected with a line segment, a polyline or a Bézier curve. The links are maintained dynamically; that is, if an object is moved, either by program or interactively, the link follows:
In the picture above, the polyline has been automatically placed to connect the two new positions of the rectangle (actually of the slots which are at a fixed distance from the rectangle). With this capability one can easily construct flowcharts or any kind of diagram that requires links between elements that can move. A good example is also the tree-like representation of hierarchies:
The graphic objects of the Widget Factory have reactive capabilities, allowing the fast design of interactive editing tools. In fact, XDrawMaker was itself designed in this way. To take a simple example, the Widget Factory rectangle supports a reactive mode that displays handles at the four corners and functionality through callback functions that are triggered before and after clicking on the handles. This functionality can then be easily used to build interactive tools such as editors.